﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using Microsoft.Phone.Controls;
using System.IO.IsolatedStorage;
using System.IO;
using System.Text;
using Microsoft.Phone.Notification;
using Microsoft.Phone.Net.NetworkInformation;

namespace NearChat
{
    public partial class Login : PhoneApplicationPage
    {
        //storage dell'applicazione
        private static IsolatedStorageSettings appSettings = IsolatedStorageSettings.ApplicationSettings;

        //canale della notifica
        private static HttpNotificationChannel httpChannel;
        private static string channelName = "NearChatChannel";
        private static Uri channelUri;

        //valori del login presi dal form
        private string user = "";
        private string psw = "";

        private bool allowGPS = false;
        private bool allowBackground = false;

        public Login()
        {
            InitializeComponent();
        }

        private void PhoneApplicationPage_Loaded(object sender, RoutedEventArgs e)
        {
            if (appSettings.Contains("user"))//arrivo dalla pagina crea account
            {
                userBox.Text = appSettings["user"].ToString();
            }

            if (NavigationService.CanGoBack)//vengo dalla main page
            {
                NavigationService.RemoveBackEntry();
            }
        }


        private void buttonAccedi_Tap(object sender, GestureEventArgs e)
        {
            //se acconsento al trattamento
            if (allowBackground && allowGPS)
            {
                //raccolgo dalla pagina
                user = userBox.Text.ToLower();//username forzato a minuscolo
                psw = pswBox.Password;

                if (NetworkInterface.GetIsNetworkAvailable())
                {
                    //prelevo il canale
                    httpChannel = HttpNotificationChannel.Find(channelName);

                    if (httpChannel == null)//canale non presente
                    {
                        httpChannel = new HttpNotificationChannel(channelName);//creo il canale

                        //creo eventi utili e assegno
                        httpChannel.ChannelUriUpdated += new EventHandler<NotificationChannelUriEventArgs>(httpChannel_ChannelUriUpdated);
                        //httpChannel.ErrorOccurred += new EventHandler<NotificationChannelErrorEventArgs>(httpChannel_ErrorOccurred);

                        httpChannel.Open();//apro il canale
                        //httpChannel.BindToShellTile();
                        httpChannel.BindToShellToast();
                    }
                    else
                    {
                        //riassegno eventi utili
                        httpChannel.ChannelUriUpdated += new EventHandler<NotificationChannelUriEventArgs>(httpChannel_ChannelUriUpdated);
                        //httpChannel.ErrorOccurred += new EventHandler<NotificationChannelErrorEventArgs>(httpChannel_ErrorOccurred);

                        channelUri = httpChannel.ChannelUri;
                    }
                    
                    //faccio request PHP al DB
                    Uri myDBuri = new Uri("http://www.nearchat.altervista.org/login.php");
                    HttpWebRequest loginRequest = (HttpWebRequest)HttpWebRequest.Create(myDBuri);
                    loginRequest.Method = "POST";
                    loginRequest.ContentType = "application/x-www-form-urlencoded";
                    loginRequest.BeginGetRequestStream(new AsyncCallback(GetRequestStreamCallback), loginRequest);
                }
                else
                    MessageBox.Show("connection error, please retry later.");
            }
            else
                MessageBox.Show("please accept GPS and Background condition.");
        }

        private void buttonCreaAccount_Tap(object sender, GestureEventArgs e)
        {
            NavigationService.Navigate(new Uri("/CreateAccount.xaml", UriKind.Relative));//cambio della pagina
        }

        void GetRequestStreamCallback(IAsyncResult callbackResult)
        {
            HttpWebRequest myRequest = (HttpWebRequest)callbackResult.AsyncState;
            // End the stream request operation
            Stream postStream = myRequest.EndGetRequestStream(callbackResult);

            // Create the post data
            string postData = "apikey=4nn!eSupp0rt&user=" + user.ToString() + "&psw=" + psw.ToString()+"&uri=" + channelUri;
            byte[] byteArray = Encoding.UTF8.GetBytes(postData);

            // Add the post data to the web request
            postStream.Write(byteArray, 0, byteArray.Length);
            postStream.Close();
            //Dispatcher.BeginInvoke(() => MessageBox.Show("GetRequestStreamCallback"));
            // Start the web request
            myRequest.BeginGetResponse(new AsyncCallback(GetResponsetStreamCallback), myRequest);
        }//GetRequestStreamCallback

        void GetResponsetStreamCallback(IAsyncResult callbackResult)
        {
            //Dispatcher.BeginInvoke(() => MessageBox.Show("GetResponsetStreamCallback"));
            HttpWebRequest request = (HttpWebRequest)callbackResult.AsyncState;
            HttpWebResponse response = (HttpWebResponse)request.EndGetResponse(callbackResult);
            using (StreamReader httpWebStreamReader = new StreamReader(response.GetResponseStream()))
            {
                string result = httpWebStreamReader.ReadToEnd();
                Dispatcher.BeginInvoke(() => ParsingLogin(result));
            }
        }//GetResponsetStreamCallback

        void ParsingLogin(string result)
        {
            if (result == "")//query vuota
                MessageBox.Show("incorrect username or password");
            else
            {
                string[] ris = majorSplit(result);
                ris = minorSplit(ris[0]);//sono sicuro che rappresenta un solo record

                if (ris[0] == "ERRORE")
                {
                    MessageBox.Show(ris[1]);
                }
                else //se login effettuato
                {
                    appSettings.Clear();

                    //aggiungo i dati in locale
                    appSettings.Add("user", user); 
                    appSettings.Add("ID", ris[0]);
                    appSettings.Add("uri", channelUri);

                    //torno indietro alla main page
                    NavigationService.Navigate(new Uri("/MainPage.xaml", UriKind.Relative));//cambio della pagina
                }
            }
        }

        private void buttonDimenticato_Click(object sender, RoutedEventArgs e)
        {
            NavigationService.Navigate(new Uri("/RecuperoPassword.xaml", UriKind.Relative));//cambio della pagina
        }//ParsingLogin

        //splitta la stringa passata in base a |
        private string[] minorSplit(string result)
        {
            return result.Split('|');
        }

        //splitta la stringa passata in base a §
        private string[] majorSplit(string result)
        {
            return result.Split('§');
        }

        private void checkBox1_Checked(object sender, RoutedEventArgs e)
        {
            allowGPS = true;
        }

        private void checkBox2_Checked(object sender, RoutedEventArgs e)
        {
            allowBackground = true;
        }

        private void checkBox1_Unchecked(object sender, RoutedEventArgs e)
        {
            allowGPS = false;
        }

        private void checkBox2_Unchecked(object sender, RoutedEventArgs e)
        {
            allowBackground = false;
        }

        void httpChannel_ChannelUriUpdated(object sender, NotificationChannelUriEventArgs e)
        {
            channelUri = e.ChannelUri;

            Dispatcher.BeginInvoke(() => MessageBox.Show("ChannelUriUpdated"));
        }//Channel_ChannelUriUpdated

        void httpChannel_ErrorOccurred(object sender, NotificationChannelErrorEventArgs e)
        {
            Dispatcher.BeginInvoke(() => MessageBox.Show("ErrorOccurred"));
        }//httpChannel_ErrorOccurred
    }
}